﻿using System;
using System.Linq;
using Kyoh.App.Crawler.Contents;
using Kyoh.Lib.Component.Traces;
using Kyoh.Lib.WinForms;
using System.Windows.Forms;
using System.IO;
using System.Reflection;
using System.Diagnostics;
using Kyoh.Lib.Plugin;

namespace Kyoh.App.Crawler
{
    public partial class SplashForm : LayeredForm
    {
        public SplashForm()
        {
            InitializeComponent();
        }

        protected override void OnLoad(EventArgs e)
        {
            SetLayeredWindow(Properties.Resources.crawler_splash);
            base.OnLoad(e);
        }
        internal Parsers Parsers { get; private set; }
        internal Redirects Redirects { get; private set; }
        internal Seekers Seekers { get; private set; }
        internal Pickers Pickers { get; private set; }

        public void InitComponents()
        {
            Parsers = new Parsers();
            Redirects = new Redirects();
            Seekers = new Seekers();
            Pickers = new Pickers();

            InitPluginManager(Parsers);
            InitPluginManager(Redirects);
            InitPluginManager(Seekers);
            InitPluginManager(Pickers);

            var anchors = new Anchors();
            var loaders = new Loaders();
            anchors.BeginInit();
            loaders.BeginInit();
            var plugins = Path.Combine(Path.GetDirectoryName(Application.ExecutablePath), "plugin");
            if (Directory.Exists(plugins))
            {
                var files = Directory.EnumerateFiles(plugins, "*", SearchOption.AllDirectories).Where(IsPluginFile).OrderByDescending(s => s);

                try { Parsers.Load(files); }
                catch (Exception exc)
                {
                    //TODO:
                    Debug.WriteLine(exc);
                }
                try { Redirects.Load(files); }
                catch (Exception exc)
                {
                    //TODO:
                    Debug.WriteLine(exc);
                }
                try { Seekers.Load(files); }
                catch (Exception exc)
                {
                    //TODO:
                    Debug.WriteLine(exc);
                }
                try { Pickers.Load(files); }
                catch (Exception exc)
                {
                    //TODO:
                    Debug.WriteLine(exc);
                }
            }

            Pickers.Load(Assembly.GetExecutingAssembly());
            var tracer = new TraceCollection();
            tracer.Clear();

        }

        private static void InitPluginManager<T>(PluginManager<T> manager)
            where T : class, IPlugin
        {
            manager.CompilerParameters.ReferencedAssemblies.Add("System.dll");
            manager.CompilerParameters.ReferencedAssemblies.Add("System.Web.dll");
            manager.CompilerParameters.ReferencedAssemblies.Add("System.Core.dll");
            manager.CompilerParameters.ReferencedAssemblies.Add("System.Drawing.dll");
            manager.CompilerParameters.ReferencedAssemblies.Add("System.ServiceModel.dll");
            manager.CompilerParameters.ReferencedAssemblies.Add("System.Xml.dll");
            manager.CompilerParameters.ReferencedAssemblies.Add("System.Xml.Linq.dll");
            manager.CompilerParameters.ReferencedAssemblies.Add("Kyoh.Lib.Component.dll");
            manager.CompilerParameters.ReferencedAssemblies.Add("Kyoh.Lib.Component.Traces.dll");
            manager.CompilerParameters.ReferencedAssemblies.Add("Kyoh.Lib.Plugin.dll");
            manager.CompilerParameters.ReferencedAssemblies.Add("Kyoh.Lib.IO.dll");
            manager.CompilerParameters.ReferencedAssemblies.Add("Kyoh.App.Crawler.Plugin.dll");

        }

        private static bool IsPluginFile(string path)
        {
            path = path.ToLower();
            return path.EndsWith(".dll") || path.EndsWith(".cs") || path.EndsWith(".py");
        }
    }
}
